package com.kelvem.saas.workbanch.core.manager.service;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.kelvem.saas.workbanch.core.SaasConstant;
import com.kelvem.saas.workbanch.core.base.BaseCriteria;
import com.kelvem.saas.workbanch.core.base.BaseService;
import com.kelvem.saas.workbanch.core.base.Page;
import com.kelvem.saas.workbanch.core.exception.SaasAssert;
import com.kelvem.saas.workbanch.core.exception.SaasException;
import com.kelvem.saas.workbanch.core.manager.dao.BizPageActionDao;
import com.kelvem.saas.workbanch.core.manager.model.BizPageActionEntity;
import com.kelvem.saas.workbanch.core.manager.model.MetaTableActionEntity;
import com.kelvem.saas.workbanch.core.manager.request.BizPageActionQueryVo;
import com.kelvem.saas.workbanch.core.utils.DateUtil;
import com.kelvem.saas.workbanch.fsm.dao.BaseDao;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Date;
import java.util.List;

/**
 * 业务页面行为Service
 *
 * @author kelvem
 * @version 1.0
 */
@Service
@Slf4j
public class BizPageActionService extends BaseService<BizPageActionEntity, BizPageActionQueryVo> {

    @Resource
    private BizPageActionDao bizPageActionDao;

    /**
     * 增加业务页面行为
     *
     * @param bizPageAction 业务页面行为信息
     * @return Long 主键
     */
    @Transactional(rollbackFor = Exception.class)
    public Long addBizPageAction(BizPageActionEntity bizPageAction) {
        
        log.info("BizPageActionService:addBizPageAction:start, bizPageAction=【{}】", bizPageAction);
        SaasAssert.notNull(bizPageAction);
        
        try {
            if (bizPageAction.getCreateTime() == null) {
                bizPageAction.setCreateTime(DateUtil.now());
            }
            if (bizPageAction.getUpdateTime() == null) {
                bizPageAction.setUpdateTime(DateUtil.now());
            }
        
            bizPageActionDao.insert(bizPageAction);
            Long bizPageActionId = bizPageAction.getId();
            log.info("BizPageActionService:addBizPageAction:end, bizPageActionId={}", bizPageActionId);
        
            return bizPageAction.getId();
        } catch (Exception e) {
            String msg = String.format("BizPageActionService:addBizPageAction:error, %s", e.getMessage());
            log.error(msg, e);
            throw new SaasException(msg);
        }
    }

    /**
     * 修改业务页面行为
     *
     * @param bizPageAction 业务页面行为信息
     * @return 更新记录数
     */
    @Transactional(rollbackFor = Exception.class)
    public int updateBizPageAction(BizPageActionEntity bizPageAction) {
        
        log.info("BizPageActionService:updateBizPageAction:start, bizPageAction=【{}】", bizPageAction);
        SaasAssert.notNull(bizPageAction);
        SaasAssert.notNull(bizPageAction.getId());

        try {
            int count = bizPageActionDao.updateById(bizPageAction);
            log.info("BizPageActionService:updateBizPageAction:end, count={}", count);
            return count;
        } catch (Exception e) {
            String msg = String.format("BizPageActionService:updateBizPageAction:error, %s", e.getMessage());
            log.error(msg, e);
            throw new SaasException(msg);
        }
    }

    /**
     * 删除业务页面行为
     *
     * @param bizPageActionId 业务页面行为id
     * @return 删除记录数
     */
    @Transactional(rollbackFor = Exception.class)
    public int deleteBizPageAction(Long bizPageActionId) {

        log.info("BizPageActionService:deleteBizPageAction:start, bizPageActionId={}", bizPageActionId);
        SaasAssert.notNull(bizPageActionId);
        
        try {
            int count = bizPageActionDao.deleteById(bizPageActionId);
            log.info("BizPageActionService:deleteBizPageAction:end, count={}", count);
            return count;
        } catch (Exception e) {
            String msg = String.format("BizPageActionService:deleteBizPageAction:error, %s", e.getMessage());
            log.error(msg, e);
            throw new SaasException(msg);
        }
    }
    
    /**
     * 查询业务页面行为分页数据
     *
     * @param bizPageActionQueryVo 查询用
     * @return Page<BizPageActionDto>
     */
    public Page<BizPageActionEntity> queryBizPageActionPage(BizPageActionQueryVo bizPageActionQueryVo) {
        
        log.info("BizPageActionService:queryBizPageActionPage:start, bizPageActionQueryVo=【{}】", bizPageActionQueryVo);
        SaasAssert.notNull(bizPageActionQueryVo);
        
        try {
            Page<BizPageActionEntity> page = super.queryPage(bizPageActionQueryVo);
            log.info("BizPageActionService:queryBizPageActionPage:end, page.size={}", page.getRecords().size());
            return page;
        } catch (Exception e) {
            String msg = String.format("BizPageActionService:queryBizPageActionPage:error, %s", e.getMessage());
            log.error(msg, e);
            throw new SaasException(msg);
        }
    }

    /**
     * 查询业务页面行为列表数据
     *
     * @param bizPageActionQueryVo 查询用
     * @return List<BizPageAction>
     */
    public List<BizPageActionEntity> queryBizPageActionList(BizPageActionQueryVo bizPageActionQueryVo) {
        
        log.info("BizPageActionService:queryBizPageActionList:start, bizPageActionQueryVo=【{}】", bizPageActionQueryVo);
        SaasAssert.notNull(bizPageActionQueryVo);
        
        try {
            List<BizPageActionEntity> list = super.queryList(bizPageActionQueryVo);
            log.info("BizPageActionService:queryBizPageActionList:end, list.size={}", list.size());
            return list;
        } catch (Exception e) {
            String msg = String.format("BizPageActionService:queryBizPageActionList:error, %s", e.getMessage());
            log.error(msg, e);
            throw new SaasException(msg);
        }
    }

    /**
     * 根据id查询业务页面行为信息
     *
     * @param bizPageActionId 业务页面行为id
     * @return BizPageAction
     */
    public BizPageActionEntity getBizPageActionById(Long bizPageActionId) {

        log.info("BizPageActionService:getBizPageActionById:start, bizPageActionId={}", bizPageActionId);
        SaasAssert.notNull(bizPageActionId);
        
        try {
            BizPageActionEntity bizPageAction = bizPageActionDao.selectById(bizPageActionId);
            log.info("BizPageActionService:getBizPageActionById:end, bizPageActionInfo=【{}】", bizPageAction);
            return bizPageAction;
        } catch (Exception e) {
            String msg = String.format("BizPageActionService:getBizPageActionById:error, %s", e.getMessage());
            log.error(msg, e);
            throw new SaasException(msg);
        }
    }

    /**
     * 构建查询用Criteria
     * 基类的queryPage, queryList方法使用
     *
     * @param queryVo 查询用
     * @return BaseCriteria
     */
    @Override
    public BaseCriteria<BizPageActionEntity> buildQueryCriteria(BizPageActionQueryVo queryVo) {
        BaseCriteria<BizPageActionEntity> criteria = new BaseCriteria<>();
        criteria.orderByDesc("id");
        
        // 主键
        Long id = queryVo.getId();
        if (super.isNotEmpty(id)) {
            criteria.andEqualTo("id", queryVo.getId());
        }
        
        // 创建时间
        Date startCreateTime = queryVo.getStartCreateTime();
        if(super.isNotEmpty(startCreateTime)) {
            criteria.andGreaterThanOrEqualTo("createTime", startCreateTime);
        }
        Date endCreateTime = queryVo.getEndCreateTime();
        if(super.isNotEmpty(endCreateTime)) {
            criteria.andLessThanOrEqualTo("createTime", endCreateTime);
        }

        // 实体业务id
        Long bizPageId = queryVo.getBizPageId();
        if (super.isNotEmpty(bizPageId)) {
            criteria.andEqualTo("bizPageId", bizPageId);
        }

        // node类型, panel;dom
        String nodeType = queryVo.getNodeType();
        if (super.isNotEmpty(nodeType)) {
            criteria.andEqualTo("nodeType", nodeType);
        }

        // 实体表id
        Long metaTableId = queryVo.getMetaTableId();
        if (super.isNotEmpty(metaTableId)) {
            criteria.andEqualTo("metaTableId", metaTableId);
        }

        // 行为类型, crud fsm sql script ...
        String actionType = queryVo.getActionType();
        if (super.isNotEmpty(actionType)) {
            criteria.andEqualTo("actionType", actionType);
        }

        // 事件触发类型, page:跳页面; dialog:弹对话框; crud:增删改查; api:调接口; fsm:调状态机; redirect:跳url; js:js方法
        String actionSubType = queryVo.getActionSubType();
        if (super.isNotEmpty(actionSubType)) {
            criteria.andEqualTo("actionSubType", actionSubType);
        }

        // 事件来源类型, system:系统; manual:人工
        String sourceType = queryVo.getSourceType();
        if (super.isNotEmpty(sourceType)) {
            criteria.andEqualTo("sourceType", sourceType);
        }

        // 关联对象类型
        String relatedType = queryVo.getRelatedType();
        if (super.isNotEmpty(relatedType)) {
            criteria.andEqualTo("relatedType", relatedType);
        }

        // 关联对象id
        Long relatedId = queryVo.getRelatedId();
        if (super.isNotEmpty(relatedId)) {
            criteria.andEqualTo("relatedId", relatedId);
        }

        // http_method
        String httpMethod = queryVo.getHttpMethod();
        if (super.isNotEmpty(httpMethod)) {
            criteria.andEqualTo("httpMethod", httpMethod);
        }

        // 参数域类型
        String scopeType = queryVo.getScopeType();
        if (super.isNotEmpty(scopeType)) {
            criteria.andEqualTo("scopeType", scopeType);
        }

        // 结果集名称
        String datasetName = queryVo.getDatasetName();
        if (super.isNotEmpty(datasetName)) {
            criteria.andEqualTo("datasetName", datasetName);
        }

        // 列展示, 1:展示; 0:不展示
        Integer showFlag = queryVo.getShowFlag();
        if (super.isNotEmpty(showFlag)) {
            criteria.andEqualTo("showFlag", showFlag);
        }

        // 创建人
        String createUid = queryVo.getCreateUid();
        if (super.isNotEmpty(createUid)) {
            criteria.andEqualTo("createUid", createUid);
        }

        // 更新人
        String updateUid = queryVo.getUpdateUid();
        if (super.isNotEmpty(updateUid)) {
            criteria.andEqualTo("updateUid", updateUid);
        }

        return criteria;
    }

    @Override
    public BaseDao<BizPageActionEntity> getDao() {
        return this.bizPageActionDao;
    }


    /**
     * 查询页面行为列表数据
     *
     * @param bizPageId 页面id
     * @return List<BizPageAction>
     */
    public List<BizPageActionEntity> queryBizPageActionList(Long bizPageId) {

        log.info("BizPageActionService:queryBizPageActionList:start, bizPageId=【{}】", bizPageId);
        SaasAssert.notNull(bizPageId);

        try {
            BizPageActionQueryVo bizPageActionQueryVo = BizPageActionQueryVo.builder().bizPageId(bizPageId).build();
            List<BizPageActionEntity> list = super.queryList(bizPageActionQueryVo);
            log.info("BizPageActionService:queryBizPageActionList:end, list.size={}", list.size());
            return list;
        } catch (Exception e) {
            String msg = String.format("BizPageActionService:queryBizPageActionList:error, %s", e.getMessage());
            log.error(msg, e);
            throw new SaasException(msg);
        }
    }

    /**
     * 通过实体业务id, 删除实体业务事件
     *
     * @param bizPageId 实体业务id
     * @return 删除记录数
     */
    @Transactional(rollbackFor = Exception.class)
    public int deleteByBizPageId(Long bizPageId) {

        log.info("BizPageActionService:deleteByBizPageId:start, bizPageId={}", bizPageId);
        SaasAssert.notNull(bizPageId);

        try {
            LambdaQueryWrapper<BizPageActionEntity> lambdaQueryWrapper = new LambdaQueryWrapper<>();
            lambdaQueryWrapper.eq(BizPageActionEntity::getBizPageId, bizPageId);
            int count = bizPageActionDao.delete(lambdaQueryWrapper);
            log.info("BizPageActionService:deleteByBizPageId:end, count={}", count);
            return count;
        } catch (Exception e) {
            String msg = String.format("BizPageActionService:deleteByBizPageId:error, %s", e.getMessage());
            log.error(msg, e);
            throw new SaasException(msg);
        }
    }

    // todo 字段设置不全
    @Transactional(rollbackFor = Exception.class)
    public List<BizPageActionEntity> addBizPageAction(Long pageId, Long templateId, Long metaTableId) {
        BizPageActionQueryVo query = BizPageActionQueryVo.builder().bizPageId(templateId).build();
        List<BizPageActionEntity> bizPageActionList = this.queryList(query);
        for (BizPageActionEntity bizPageAction:
                bizPageActionList) {
            bizPageAction.setId(null);
            bizPageAction.setBizPageId(pageId);
            bizPageAction.setMetaTableId(metaTableId);

//            bizPageAction.setTableEventId();  todo -> event_no

            bizPageAction.setSourceType("");

//            bizPageAction.setRelatedId(null); // todo 无用


            this.addBizPageAction(bizPageAction);
        }
        return bizPageActionList;
    }

    // todo 字段设置不全
    public BizPageActionEntity convert(MetaTableActionEntity metaTableAction, Long bizPageId) {

        BizPageActionEntity action = new BizPageActionEntity();
        action.setShowFlag(SaasConstant.FLAG_YES);
        action.setBizPageId(bizPageId);
        action.setRelatedId(metaTableAction.getId());
        action.setMetaTableId(metaTableAction.getMetaTableId());
        action.setEventName(metaTableAction.getActionName());
        action.setUrl(metaTableAction.getParamUrl());
        action.setSortNo(metaTableAction.getSortNo());
        action.setMemo("");

        return action;
    }

}
